"""
DaoMath Space Theory (道数空间理论)
从 ±0 先天均衡构造空间层级

空间层级:
    ±0 (先天均衡)
     ↓
    集合 (Set) - 离散空间
     ↓
    拓扑空间 (Topological Space) - 连续性概念
     ↓
    度量空间 (Metric Space) - 距离概念
     ↓
    赋范空间 (Normed Space) - 长度概念
     ↓
    内积空间 (Inner Product Space) - 角度概念
     ↓
    Hilbert空间 - 完备的内积空间
     ↓
    流形 (Manifold) - 局部欧式的曲面
"""

from __future__ import annotations
from typing import (
    TypeVar, Generic, Callable, Set, List, Tuple, 
    Optional, Iterator, Dict, Any, Protocol
)
from dataclasses import dataclass, field
from abc import ABC, abstractmethod
from enum import Enum
import numpy as np
from itertools import combinations, chain

from core.axioms import InnateBalance, DualPair
from structures.number import Real, Complex


T = TypeVar('T')
U = TypeVar('U')


# ============================================================================
# Level 0: 集合论基础 (Set Theory)
# ============================================================================

class DaoSet(Generic[T]):
    """
    基于 ±0 的集合
    
    集合的三元结构:
    - 元素集 (正向)
    - 补集 (负向)
    - 空集 (中性)
    """
    
    def __init__(self, elements: Set[T], universe: Optional[Set[T]] = None):
        self.elements = elements
        self.universe = universe if universe else elements
    
    def complement(self) -> DaoSet[T]:
        """补集 (对偶)"""
        if self.universe:
            return DaoSet(self.universe - self.elements, self.universe)
        raise ValueError("Universe not defined for complement")
    
    def union(self, other: DaoSet[T]) -> DaoSet[T]:
        """并集"""
        new_universe = self.universe | other.universe
        return DaoSet(self.elements | other.elements, new_universe)
    
    def intersection(self, other: DaoSet[T]) -> DaoSet[T]:
        """交集"""
        return DaoSet(
            self.elements & other.elements,
            self.universe & other.universe
        )
    
    def difference(self, other: DaoSet[T]) -> DaoSet[T]:
        """差集"""
        return DaoSet(self.elements - other.elements, self.universe)
    
    def symmetric_difference(self, other: DaoSet[T]) -> DaoSet[T]:
        """对称差 (平衡运算)"""
        return DaoSet(
            (self.elements - other.elements) | (other.elements - self.elements),
            self.universe | other.universe
        )
    
    def cardinality(self) -> int:
        """基数"""
        return len(self.elements)
    
    def power_set(self) -> DaoSet[DaoSet[T]]:
        """幂集"""
        elem_list = list(self.elements)
        subsets = []
        for i in range(len(elem_list) + 1):
            for subset in combinations(elem_list, i):
                subsets.append(DaoSet(set(subset), self.universe))
        return DaoSet(set(subsets))
    
    def __contains__(self, item: T) -> bool:
        return item in self.elements
    
    def __len__(self) -> int:
        return len(self.elements)
    
    def __repr__(self) -> str:
        if len(self.elements) <= 10:
            return f"DaoSet({self.elements})"
        else:
            return f"DaoSet({len(self.elements)} elements)"


# ============================================================================
# Level 1: 拓扑空间 (Topological Space)
# ============================================================================

class Topology(Generic[T]):
    """
    拓扑: 开集族
    
    拓扑公理:
    T1. ∅ ∈ τ, X ∈ τ (空集和全集是开集)
    T2. 任意多个开集的并是开集
    T3. 有限个开集的交是开集
    """
    
    def __init__(self, base_set: Set[T], open_sets: Set[frozenset[T]]):
        self.base_set = base_set
        self.open_sets = open_sets
        
        if not self.verify_axioms():
            raise ValueError("Invalid topology: axioms not satisfied")
    
    def verify_axioms(self) -> bool:
        """验证拓扑公理"""
        # T1: 空集和全集必须在开集族中
        if frozenset() not in self.open_sets:
            return False
        if frozenset(self.base_set) not in self.open_sets:
            return False
        
        # T2 和 T3 难以直接验证，假设构造时正确
        return True
    
    def is_open(self, subset: Set[T]) -> bool:
        """判断是否为开集"""
        return frozenset(subset) in self.open_sets
    
    def is_closed(self, subset: Set[T]) -> bool:
        """判断是否为闭集 (开集的补集)"""
        complement = self.base_set - subset
        return self.is_open(complement)
    
    def interior(self, subset: Set[T]) -> Set[T]:
        """内部: 包含在subset中的最大开集"""
        interior_sets = [
            s for s in self.open_sets 
            if s.issubset(subset)
        ]
        if interior_sets:
            return set.union(*interior_sets)
        return set()
    
    def closure(self, subset: Set[T]) -> Set[T]:
        """闭包: 包含subset的最小闭集"""
        # 闭包 = 所有包含subset的闭集的交
        closed_sets = []
        for open_set in self.open_sets:
            complement = self.base_set - set(open_set)
            if subset.issubset(complement):
                closed_sets.append(complement)
        
        if closed_sets:
            return set.intersection(*closed_sets)
        return self.base_set
    
    def boundary(self, subset: Set[T]) -> Set[T]:
        """边界: 闭包 - 内部"""
        return self.closure(subset) - self.interior(subset)
    
    @staticmethod
    def discrete_topology(base_set: Set[T]) -> Topology[T]:
        """离散拓扑: 所有子集都是开集"""
        from itertools import chain, combinations
        
        def powerset(s):
            return chain.from_iterable(
                combinations(s, r) for r in range(len(s) + 1)
            )
        
        all_subsets = {frozenset(subset) for subset in powerset(base_set)}
        return Topology(base_set, all_subsets)
    
    @staticmethod
    def trivial_topology(base_set: Set[T]) -> Topology[T]:
        """平凡拓扑: 只有空集和全集是开集"""
        return Topology(
            base_set,
            {frozenset(), frozenset(base_set)}
        )
    
    @staticmethod
    def cofinite_topology(base_set: Set[T]) -> Topology[T]:
        """余有限拓扑: 补集为有限集的集合是开集"""
        open_sets = {frozenset(), frozenset(base_set)}
        
        # 添加所有余有限集
        for subset in combinations(base_set, len(base_set) - 1):
            open_sets.add(frozenset(subset))
        
        return Topology(base_set, open_sets)


class TopologicalSpace(Generic[T]):
    """
    拓扑空间: (X, τ)
    
    基于 ±0 的拓扑空间理论:
    - 开集 ↔ 正向 (扩张)
    - 闭集 ↔ 负向 (收缩)
    - 边界 ↔ 均衡态
    """
    
    def __init__(self, base_set: Set[T], topology: Topology[T]):
        self.base_set = base_set
        self.topology = topology
    
    def is_hausdorff(self) -> bool:
        """
        Hausdorff性质 (T2空间):
        任意两个不同点都有不相交的邻域
        """
        # 简化检查：对于小集合
        if len(self.base_set) > 10:
            return True  # 假设成立
        
        for x in self.base_set:
            for y in self.base_set:
                if x != y:
                    # 寻找分离的开集
                    found_separation = False
                    for U in self.topology.open_sets:
                        for V in self.topology.open_sets:
                            if (x in U and y in V and 
                                len(U & V) == 0):
                                found_separation = True
                                break
                        if found_separation:
                            break
                    if not found_separation:
                        return False
        return True
    
    def is_compact(self) -> bool:
        """
        紧致性: 每个开覆盖都有有限子覆盖
        
        对于有限空间，自动紧致
        """
        return len(self.base_set) < float('inf')
    
    def is_connected(self) -> bool:
        """
        连通性: 不能表示为两个非空不相交开集的并
        """
        for U in self.topology.open_sets:
            if U and U != frozenset(self.base_set):
                V = frozenset(self.base_set) - U
                if self.topology.is_open(set(V)):
                    return False
        return True
    
    def connected_components(self) -> List[Set[T]]:
        """连通分支"""
        # 简化实现：使用并查集
        components = []
        remaining = set(self.base_set)
        
        while remaining:
            component = {remaining.pop()}
            changed = True
            
            while changed:
                changed = False
                for x in list(component):
                    for y in remaining:
                        # 检查是否在同一连通分支
                        if self._are_connected(x, y):
                            component.add(y)
                            remaining.remove(y)
                            changed = True
                            break
            
            components.append(component)
        
        return components
    
    def _are_connected(self, x: T, y: T) -> bool:
        """检查两点是否连通"""
        # 简化：假设在同一开集中即连通
        for open_set in self.topology.open_sets:
            if x in open_set and y in open_set:
                return True
        return False


# ============================================================================
# Level 2: 度量空间 (Metric Space)
# ============================================================================

class Metric(Generic[T], ABC):
    """
    度量（距离函数）
    
    度量公理:
    M1. d(x,y) ≥ 0 (非负性)
    M2. d(x,y) = 0 ⟺ x = y (同一性)
    M3. d(x,y) = d(y,x) (对称性)
    M4. d(x,z) ≤ d(x,y) + d(y,z) (三角不等式)
    """
    
    @abstractmethod
    def distance(self, x: T, y: T) -> float:
        """计算距离"""
        pass
    
    def verify_axioms(self, x: T, y: T, z: T) -> Dict[str, bool]:
        """验证度量公理"""
        dxy = self.distance(x, y)
        dyx = self.distance(y, x)
        dxz = self.distance(x, z)
        dyz = self.distance(y, z)
        dxx = self.distance(x, x)
        
        return {
            'M1_non_negative': dxy >= 0,
            'M2_identity': dxx == 0 and (dxy == 0) == (x == y),
            'M3_symmetric': abs(dxy - dyx) < 1e-10,
            'M4_triangle': dxz <= dxy + dyz + 1e-10
        }


class EuclideanMetric(Metric[np.ndarray]):
    """欧几里得度量: d(x,y) = ||x - y||₂"""
    
    def distance(self, x: np.ndarray, y: np.ndarray) -> float:
        return float(np.linalg.norm(x - y))


class ManhattanMetric(Metric[np.ndarray]):
    """曼哈顿度量: d(x,y) = Σ|xᵢ - yᵢ|"""
    
    def distance(self, x: np.ndarray, y: np.ndarray) -> float:
        return float(np.sum(np.abs(x - y)))


class ChebyshevMetric(Metric[np.ndarray]):
    """切比雪夫度量: d(x,y) = max|xᵢ - yᵢ|"""
    
    def distance(self, x: np.ndarray, y: np.ndarray) -> float:
        return float(np.max(np.abs(x - y)))


class DiscreteMetric(Metric[T]):
    """离散度量: d(x,y) = 0 if x=y else 1"""
    
    def distance(self, x: T, y: T) -> float:
        return 0.0 if x == y else 1.0


class MetricSpace(Generic[T]):
    """
    度量空间: (X, d)
    
    度量空间诱导拓扑:
    开球 B(x, r) = {y ∈ X : d(x,y) < r} 构成拓扑基
    """
    
    def __init__(self, base_set: Set[T], metric: Metric[T]):
        self.base_set = base_set
        self.metric = metric
    
    def open_ball(self, center: T, radius: float) -> Set[T]:
        """开球: B(x, r) = {y : d(x,y) < r}"""
        return {
            y for y in self.base_set
            if self.metric.distance(center, y) < radius
        }
    
    def closed_ball(self, center: T, radius: float) -> Set[T]:
        """闭球: B̄(x, r) = {y : d(x,y) ≤ r}"""
        return {
            y for y in self.base_set
            if self.metric.distance(center, y) <= radius
        }
    
    def sphere(self, center: T, radius: float) -> Set[T]:
        """球面: S(x, r) = {y : d(x,y) = r}"""
        return {
            y for y in self.base_set
            if abs(self.metric.distance(center, y) - radius) < 1e-10
        }
    
    def diameter(self) -> float:
        """直径: sup{d(x,y) : x,y ∈ X}"""
        if len(self.base_set) > 100:
            # 采样计算
            sample = list(self.base_set)[:100]
            return max(
                self.metric.distance(x, y)
                for x in sample for y in sample
            )
        
        return max(
            self.metric.distance(x, y)
            for x in self.base_set for y in self.base_set
        )
    
    def is_bounded(self) -> bool:
        """有界性"""
        return self.diameter() < float('inf')
    
    def is_complete(self) -> bool:
        """
        完备性: 每个Cauchy序列都收敛
        
        简化：假设有限空间完备
        """
        return len(self.base_set) < float('inf')
    
    def induced_topology(self) -> Topology[T]:
        """诱导拓扑"""
        # 生成所有开球的并
        open_sets = {frozenset(), frozenset(self.base_set)}
        
        # 为每个点生成一些开球
        for point in self.base_set:
            for radius in [0.1, 0.5, 1.0, 2.0, 5.0]:
                ball = self.open_ball(point, radius)
                if ball:
                    open_sets.add(frozenset(ball))
        
        return Topology(self.base_set, open_sets)
    
    def lipschitz_constant(
        self, 
        f: Callable[[T], T], 
        sample_size: int = 100
    ) -> Optional[float]:
        """
        Lipschitz常数: inf{L : d(f(x),f(y)) ≤ L·d(x,y)}
        """
        if len(self.base_set) <= sample_size:
            sample = list(self.base_set)
        else:
            sample = list(self.base_set)[:sample_size]
        
        L = 0.0
        for x in sample:
            for y in sample:
                if x != y:
                    dxy = self.metric.distance(x, y)
                    dfxy = self.metric.distance(f(x), f(y))
                    if dxy > 1e-10:
                        L = max(L, dfxy / dxy)
        
        return L if L < float('inf') else None


# ============================================================================
# Level 3: 赋范空间 (Normed Space)
# ============================================================================

class Norm(Generic[T], ABC):
    """
    范数
    
    范数公理:
    N1. ||x|| ≥ 0 (非负性)
    N2. ||x|| = 0 ⟺ x = 0 (正定性)
    N3. ||αx|| = |α|·||x|| (齐次性)
    N4. ||x + y|| ≤ ||x|| + ||y|| (三角不等式)
    """
    
    @abstractmethod
    def norm(self, x: T) -> float:
        """计算范数"""
        pass
    
    def verify_axioms(
        self, 
        x: T, 
        y: T, 
        alpha: float,
        zero: T
    ) -> Dict[str, bool]:
        """验证范数公理"""
        nx = self.norm(x)
        ny = self.norm(y)
        nzero = self.norm(zero)
        
        return {
            'N1_non_negative': nx >= 0,
            'N2_positive_definite': nzero == 0,
            'N3_homogeneous': True,  # 需要实际计算 ||αx||
            'N4_triangle': self.norm(x) <= nx + ny  # 简化
        }


class LpNorm(Norm[np.ndarray]):
    """Lp 范数: ||x||_p = (Σ|xᵢ|^p)^(1/p)"""
    
    def __init__(self, p: float = 2.0):
        if p < 1:
            raise ValueError("p must be >= 1")
        self.p = p
    
    def norm(self, x: np.ndarray) -> float:
        if self.p == float('inf'):
            return float(np.max(np.abs(x)))
        return float(np.sum(np.abs(x) ** self.p) ** (1 / self.p))


class NormedSpace(Generic[T]):
    """
    赋范空间: (V, ||·||)
    
    赋范空间诱导度量: d(x,y) = ||x - y||
    """
    
    def __init__(
        self, 
        base_set: Set[T], 
        norm: Norm[T],
        add: Callable[[T, T], T],
        scale: Callable[[float, T], T],
        zero: T
    ):
        self.base_set = base_set
        self.norm = norm
        self.add = add
        self.scale = scale
        self.zero = zero
    
    def induced_metric(self) -> Metric[T]:
        """诱导度量"""
        class InducedMetric(Metric[T]):
            def __init__(self, normed_space: NormedSpace[T]):
                self.space = normed_space
            
            def distance(self, x: T, y: T) -> float:
                # d(x,y) = ||x - y||
                diff = self.space.add(x, self.space.scale(-1, y))
                return self.space.norm.norm(diff)
        
        return InducedMetric(self)
    
    def unit_ball(self) -> Set[T]:
        """单位球: {x : ||x|| ≤ 1}"""
        return {x for x in self.base_set if self.norm.norm(x) <= 1}
    
    def unit_sphere(self) -> Set[T]:
        """单位球面: {x : ||x|| = 1}"""
        return {
            x for x in self.base_set 
            if abs(self.norm.norm(x) - 1) < 1e-10
        }


# ============================================================================
# Level 4: 内积空间 (Inner Product Space)
# ============================================================================

class InnerProduct(Generic[T], ABC):
    """
    内积
    
    内积公理:
    I1. ⟨x,x⟩ ≥ 0 (正定性)
    I2. ⟨x,y⟩ = ⟨y,x⟩* (共轭对称性)
    I3. ⟨αx + βy, z⟩ = α⟨x,z⟩ + β⟨y,z⟩ (线性性)
    """
    
    @abstractmethod
    def inner_product(self, x: T, y: T) -> complex:
        """计算内积"""
        pass
    
    def induced_norm(self, x: T) -> float:
        """诱导范数: ||x|| = √⟨x,x⟩"""
        return float(np.sqrt(abs(self.inner_product(x, x))))


class EuclideanInnerProduct(InnerProduct[np.ndarray]):
    """欧几里得内积: ⟨x,y⟩ = Σ xᵢyᵢ"""
    
    def inner_product(self, x: np.ndarray, y: np.ndarray) -> complex:
        return complex(np.dot(x, y))


class InnerProductSpace(Generic[T]):
    """
    内积空间: (V, ⟨·,·⟩)
    
    内积空间 → 赋范空间 → 度量空间 → 拓扑空间
    """
    
    def __init__(
        self,
        base_set: Set[T],
        inner_product: InnerProduct[T],
        add: Callable[[T, T], T],
        scale: Callable[[complex, T], T],
        zero: T
    ):
        self.base_set = base_set
        self.inner_product = inner_product
        self.add = add
        self.scale = scale
        self.zero = zero
    
    def induced_norm(self) -> Norm[T]:
        """诱导范数"""
        class InducedNorm(Norm[T]):
            def __init__(self, inner_product: InnerProduct[T]):
                self.ip = inner_product
            
            def norm(self, x: T) -> float:
                return self.ip.induced_norm(x)
        
        return InducedNorm(self.inner_product)
    
    def angle(self, x: T, y: T) -> float:
        """
        夹角: cos(θ) = ⟨x,y⟩ / (||x|| ||y||)
        """
        ip = self.inner_product.inner_product(x, y)
        nx = self.inner_product.induced_norm(x)
        ny = self.inner_product.induced_norm(y)
        
        if nx < 1e-10 or ny < 1e-10:
            return 0.0
        
        cos_theta = abs(ip) / (nx * ny)
        return float(np.arccos(np.clip(cos_theta, -1, 1)))
    
    def is_orthogonal(self, x: T, y: T, tol: float = 1e-10) -> bool:
        """判断正交: ⟨x,y⟩ = 0"""
        return abs(self.inner_product.inner_product(x, y)) < tol
    
    def projection(self, x: T, y: T) -> T:
        """
        投影: proj_y(x) = (⟨x,y⟩/⟨y,y⟩)·y
        """
        ip_xy = self.inner_product.inner_product(x, y)
        ip_yy = self.inner_product.inner_product(y, y)
        
        if abs(ip_yy) < 1e-10:
            return self.zero
        
        coeff = ip_xy / ip_yy
        return self.scale(coeff, y)
    
    def gram_schmidt(self, vectors: List[T]) -> List[T]:
        """
        Gram-Schmidt正交化
        """
        orthogonal = []
        
        for v in vectors:
            # 减去在已有正交向量上的投影
            w = v
            for u in orthogonal:
                proj = self.projection(v, u)
                w = self.add(w, self.scale(-1, proj))
            
            # 归一化
            norm = self.inner_product.induced_norm(w)
            if norm > 1e-10:
                w = self.scale(1/norm, w)
                orthogonal.append(w)
        
        return orthogonal


# ============================================================================
# Level 5: Hilbert 空间
# ============================================================================

class HilbertSpace(InnerProductSpace[T]):
    """
    Hilbert空间: 完备的内积空间
    
    关键性质:
    - 内积空间
    - 完备性（Cauchy序列收敛）
    - 可分离性（有可数稠密子集）
    """
    
    def __init__(
        self,
        base_set: Set[T],
        inner_product: InnerProduct[T],
        add: Callable[[T, T], T],
        scale: Callable[[complex, T], T],
        zero: T,
        is_complete: bool = True
    ):
        super().__init__(base_set, inner_product, add, scale, zero)
        self.is_complete = is_complete
    
    def riesz_representation(
        self, 
        functional: Callable[[T], complex]
    ) -> Optional[T]:
        """
        Riesz表示定理: 
        每个连续线性泛函都可表示为内积
        φ(x) = ⟨x, y⟩ for some y ∈ H
        """
        # 简化实现：寻找表示元素
        for y in list(self.base_set)[:100]:  # 采样
            # 检查是否满足表示
            is_representation = True
            for x in list(self.base_set)[:10]:
                ip = self.inner_product.inner_product(x, y)
                f_x = functional(x)
                if abs(ip - f_x) > 1e-6:
                    is_representation = False
                    break
            
            if is_representation:
                return y
        
        return None
    
    def orthonormal_basis(self) -> List[T]:
        """构造标准正交基"""
        # 从base_set中选择线性无关向量
        vectors = list(self.base_set)[:10]  # 限制大小
        return self.gram_schmidt(vectors)
    
    def fourier_coefficient(self, x: T, basis_element: T) -> complex:
        """Fourier系数: ⟨x, eₙ⟩"""
        return self.inner_product.inner_product(x, basis_element)
    
    def fourier_series(self, x: T, basis: List[T]) -> List[complex]:
        """Fourier级数展开"""
        return [self.fourier_coefficient(x, e) for e in basis]


# ============================================================================
# Level 6: 流形 (Manifold)
# ============================================================================

class Chart(Generic[T]):
    """
    坐标卡: (U, φ)
    
    U: 流形上的开集
    φ: U → ℝⁿ 的同胚映射
    """
    
    def __init__(
        self,
        domain: Set[T],
        chart_map: Callable[[T], np.ndarray],
        inverse_map: Optional[Callable[[np.ndarray], T]] = None
    ):
        self.domain = domain
        self.chart_map = chart_map
        self.inverse_map = inverse_map
    
    def __call__(self, point: T) -> np.ndarray:
        """坐标映射"""
        return self.chart_map(point)
    
    def inverse(self, coords: np.ndarray) -> T:
        """逆映射"""
        if self.inverse_map is None:
            raise NotImplementedError("Inverse map not defined")
        return self.inverse_map(coords)


class Atlas(Generic[T]):
    """
    图册: 坐标卡的集合
    
    相容性: 转移映射 φⱼ ∘ φᵢ⁻¹ 是光滑的
    """
    
    def __init__(self, charts: List[Chart[T]]):
        self.charts = charts
    
    def transition_map(
        self, 
        chart_i: Chart[T], 
        chart_j: Chart[T]
    ) -> Callable[[np.ndarray], np.ndarray]:
        """
        转移映射: φⱼ ∘ φᵢ⁻¹
        """
        def transition(coords: np.ndarray) -> np.ndarray:
            point = chart_i.inverse(coords)
            return chart_j(point)
        
        return transition
    
    def is_smooth_atlas(self) -> bool:
        """检查是否为光滑图册"""
        # 简化：假设所有转移映射光滑
        return True


class Manifold(Generic[T]):
    """
    流形: 局部欧式的空间
    
    n维流形: 每点有邻域同胚于 ℝⁿ
    """
    
    def __init__(
        self,
        base_set: Set[T],
        atlas: Atlas[T],
        dimension: int
    ):
        self.base_set = base_set
        self.atlas = atlas
        self.dimension = dimension
    
    def tangent_space_dim(self) -> int:
        """切空间维数 = 流形维数"""
        return self.dimension
    
    def is_orientable(self) -> bool:
        """可定向性"""
        # 简化：检查转移映射的行列式符号
        return True
    
    @staticmethod
    def sphere(n: int) -> Manifold[Tuple[float, ...]]:
        """
        n维球面 Sⁿ
        
        Sⁿ = {x ∈ ℝⁿ⁺¹ : ||x|| = 1}
        """
        # 生成球面上的点
        if n == 1:
            # S¹: 单位圆
            points = {
                (np.cos(theta), np.sin(theta))
                for theta in np.linspace(0, 2*np.pi, 100)
            }
        elif n == 2:
            # S²: 单位球面
            points = set()
            for theta in np.linspace(0, 2*np.pi, 20):
                for phi in np.linspace(0, np.pi, 20):
                    x = np.sin(phi) * np.cos(theta)
                    y = np.sin(phi) * np.sin(theta)
                    z = np.cos(phi)
                    points.add((x, y, z))
        else:
            # 高维球面（简化）
            points = {tuple([0.0] * (n+1))}
        
        # 创建坐标卡（立体投影）
        def stereographic_projection(point: Tuple[float, ...]) -> np.ndarray:
            # 从北极投影
            coords = np.array(point[:-1]) / (1 - point[-1] + 1e-10)
            return coords
        
        chart = Chart(
            domain=points,
            chart_map=stereographic_projection
        )
        
        atlas = Atlas([chart])
        
        return Manifold(points, atlas, n)
    
    @staticmethod
    def torus() -> Manifold[Tuple[float, float]]:
        """
        环面 T² = S¹ × S¹
        """
        points = {
            (theta, phi)
            for theta in np.linspace(0, 2*np.pi, 50)
            for phi in np.linspace(0, 2*np.pi, 50)
        }
        
        def chart_map(point: Tuple[float, float]) -> np.ndarray:
            return np.array(point)
        
        chart = Chart(domain=points, chart_map=chart_map)
        atlas = Atlas([chart])
        
        return Manifold(points, atlas, 2)


# ============================================================================
# 空间层级管理器
# ============================================================================

class SpaceHierarchy:
    """
    空间理论层级管理器
    
    展示从集合到流形的完整构造过程
    """
    
    def __init__(self):
        self.levels = {
            0: ('Set', '集合'),
            1: ('Topological Space', '拓扑空间'),
            2: ('Metric Space', '度量空间'),
            3: ('Normed Space', '赋范空间'),
            4: ('Inner Product Space', '内积空间'),
            5: ('Hilbert Space', 'Hilbert空间'),
            6: ('Manifold', '流形')
        }
    
    def show_construction_path(self) -> str:
        """显示构造路径"""
        lines = []
        lines.append("=" * 70)
        lines.append("Space Theory Hierarchy Construction from ±0")
        lines.append("=" * 70)
        
        for level, (eng_name, chi_name) in self.levels.items():
            lines.append(f"\nLevel {level}: {eng_name} ({chi_name})")
            
            if level == 0:
                lines.append("  • Foundation: Set with complement (dual)")
                lines.append("  • Operations: ∪, ∩, \\ (union, intersection, difference)")
            elif level == 1:
                lines.append("  • Add: Topology τ (open sets)")
                lines.append("  • Concepts: continuity, compactness, connectedness")
            elif level == 2:
                lines.append("  • Add: Metric d(x,y) (distance)")
                lines.append("  • Properties: completeness, boundedness")
            elif level == 3:
                lines.append("  • Add: Norm ||x|| (length)")
                lines.append("  • Structure: vector space with norm")
            elif level == 4:
                lines.append("  • Add: Inner product ⟨x,y⟩ (angle)")
                lines.append("  • Operations: projection, orthogonalization")
            elif level == 5:
                lines.append("  • Add: Completeness")
                lines.append("  • Theorems: Riesz representation")
            elif level == 6:
                lines.append("  • Structure: locally Euclidean")
                lines.append("  • Examples: spheres, tori")
        
        lines.append("\n" + "=" * 70)
        return "\n".join(lines)
    
    def demonstrate_all_levels(self) -> Dict[str, Any]:
        """演示所有层级"""
        results = {}
        
        # Level 0: Set
        base_set = DaoSet({1, 2, 3, 4, 5}, {1, 2, 3, 4, 5, 6, 7, 8, 9, 10})
        results['Level_0_Set'] = {
            'set': base_set,
            'complement': base_set.complement(),
            'cardinality': base_set.cardinality()
        }
        
        # Level 1: Topological Space
        top = Topology.discrete_topology({1, 2, 3, 4, 5})
        top_space = TopologicalSpace({1, 2, 3, 4, 5}, top)
        results['Level_1_Topology'] = {
            'is_hausdorff': top_space.is_hausdorff(),
            'is_compact': top_space.is_compact(),
            'is_connected': top_space.is_connected()
        }
        
        # Level 2: Metric Space
        points = {
            np.array([0., 0.]),
            np.array([1., 0.]),
            np.array([0., 1.]),
            np.array([1., 1.])
        }
        metric_space = MetricSpace(points, EuclideanMetric())
        results['Level_2_Metric'] = {
            'diameter': metric_space.diameter(),
            'is_bounded': metric_space.is_bounded()
        }
        
        # Level 3: Normed Space
        lp_norm = LpNorm(p=2.0)
        results['Level_3_Normed'] = {
            'L2_norm_of_[3,4]': lp_norm.norm(np.array([3., 4.]))
        }
        
        # Level 4: Inner Product Space
        results['Level_4_InnerProduct'] = {
            'euclidean_inner_product': 'Available'
        }
        
        # Level 5: Hilbert Space
        results['Level_5_Hilbert'] = {
            'completeness': 'Required for Hilbert space'
        }
        
        # Level 6: Manifold
        sphere = Manifold.sphere(2)
        results['Level_6_Manifold'] = {
            'sphere_dimension': sphere.dimension,
            'torus_dimension': Manifold.torus().dimension
        }
        
        return results


# ============================================================================
# 使用示例与测试
# ============================================================================

def main():
    """主函数：演示空间理论"""
    
    print("=" * 70)
    print("DaoMath Space Theory")
    print("从 ±0 构造空间层级")
    print("=" * 70)
    print()
    
    # 1. 显示层级结构
    hierarchy = SpaceHierarchy()
    print(hierarchy.show_construction_path())
    print()
    
    # 2. Level 0: 集合
    print("\n" + "=" * 70)
    print("Level 0: 集合 (Set)")
    print("=" * 70)
    S = DaoSet({1, 2, 3, 4, 5}, {1, 2, 3, 4, 5, 6, 7, 8, 9, 10})
    print(f"集合 S: {S}")
    print(f"补集 S': {S.complement()}")
    print(f"基数 |S|: {S.cardinality()}")
    
    T = DaoSet({4, 5, 6, 7}, {1, 2, 3, 4, 5, 6, 7, 8, 9, 10})
    print(f"\n集合 T: {T}")
    print(f"S ∪ T: {S.union(T)}")
    print(f"S ∩ T: {S.intersection(T)}")
    print(f"S △ T (对称差): {S.symmetric_difference(T)}")
    
    # 3. Level 1: 拓扑空间
    print("\n" + "=" * 70)
    print("Level 1: 拓扑空间 (Topological Space)")
    print("=" * 70)
    
    base = {1, 2, 3, 4, 5}
    discrete_top = Topology.discrete_topology(base)
    print(f"离散拓扑 on {base}")
    print(f"是否 Hausdorff: {TopologicalSpace(base, discrete_top).is_hausdorff()}")
    print(f"是否紧致: {TopologicalSpace(base, discrete_top).is_compact()}")
    
    # 4. Level 2: 度量空间
    print("\n" + "=" * 70)
    print("Level 2: 度量空间 (Metric Space)")
    print("=" * 70)
    
    points = {
        np.array([0., 0.]),
        np.array([1., 0.]),
        np.array([0., 1.]),
        np.array([1., 1.])
    }
    
    euclidean = EuclideanMetric()
    metric_space = MetricSpace(points, euclidean)
    
    p1 = np.array([0., 0.])
    p2 = np.array([1., 1.])
    print(f"点集: 4个点形成正方形")
    print(f"欧几里得距离 d([0,0], [1,1]) = {euclidean.distance(p1, p2):.4f}")
    print(f"空间直径: {metric_space.diameter():.4f}")
    print(f"是否有界: {metric_space.is_bounded()}")
    
    # 验证度量公理
    p3 = np.array([1., 0.])
    axioms = euclidean.verify_axioms(p1, p2, p3)
    print(f"\n度量公理验证:")
    for axiom, satisfied in axioms.items():
        print(f"  • {axiom}: {satisfied}")
    
    # 5. Level 3: 赋范空间
    print("\n" + "=" * 70)
    print("Level 3: 赋范空间 (Normed Space)")
    print("=" * 70)
    
    v = np.array([3., 4.])
    print(f"向量 v = {v}")
    
    l1_norm = LpNorm(p=1)
    l2_norm = LpNorm(p=2)
    linf_norm = LpNorm(p=float('inf'))
    
    print(f"L¹ 范数 ||v||₁ = {l1_norm.norm(v):.4f}")
    print(f"L² 范数 ||v||₂ = {l2_norm.norm(v):.4f}")
    print(f"L∞ 范数 ||v||∞ = {linf_norm.norm(v):.4f}")
    
    # 6. Level 4: 内积空间
    print("\n" + "=" * 70)
    print("Level 4: 内积空间 (Inner Product Space)")
    print("=" * 70)
    
    x = np.array([1., 0.])
    y = np.array([1., 1.])
    
    euclidean_ip = EuclideanInnerProduct()
    print(f"向量 x = {x}")
    print(f"向量 y = {y}")
    print(f"内积 ⟨x,y⟩ = {euclidean_ip.inner_product(x, y)}")
    print(f"诱导范数 ||x|| = {euclidean_ip.induced_norm(x):.4f}")
    print(f"诱导范数 ||y|| = {euclidean_ip.induced_norm(y):.4f}")
    
    # 构造内积空间
    vector_set = {
        np.array([1., 0.]),
        np.array([0., 1.]),
        np.array([1., 1.])
    }
    
    ip_space = InnerProductSpace(
        base_set=vector_set,
        inner_product=euclidean_ip,
        add=lambda a, b: a + b,
        scale=lambda c, v: c * v,
        zero=np.array([0., 0.])
    )
    
    angle = ip_space.angle(x, y)
    print(f"\n夹角 ∠(x,y) = {np.degrees(angle):.2f}°")
    print(f"是否正交: {ip_space.is_orthogonal(x, y)}")
    
    # Gram-Schmidt正交化
    vectors = [
        np.array([1., 1.]),
        np.array([1., 0.])
    ]
    orthogonal = ip_space.gram_schmidt(vectors)
    print(f"\nGram-Schmidt正交化:")
    for i, v in enumerate(orthogonal):
        print(f"  e_{i} = {v}")
    
    # 7. Level 5: Hilbert空间
    print("\n" + "=" * 70)
    print("Level 5: Hilbert空间")
    print("=" * 70)
    print("Hilbert空间 = 完备的内积空间")
    print("关键定理: Riesz表示定理")
    print("应用: 量子力学状态空间")
    
    # 8. Level 6: 流形
    print("\n" + "=" * 70)
    print("Level 6: 流形 (Manifold)")
    print("=" * 70)
    
    sphere = Manifold.sphere(2)
    print(f"2维球面 S²:")
    print(f"  • 维数: {sphere.dimension}")
    print(f"  • 切空间维数: {sphere.tangent_space_dim()}")
    print(f"  • 可定向: {sphere.is_orientable()}")
    
    torus = Manifold.torus()
    print(f"\n环面 T²:")
    print(f"  • 维数: {torus.dimension}")
    print(f"  • 结构: S¹ × S¹")
    
    # 9. 层级演示
    print("\n" + "=" * 70)
    print("完整层级演示")
    print("=" * 70)
    
    demo_results = hierarchy.demonstrate_all_levels()
    for level, results in demo_results.items():
        print(f"\n{level}:")
        if isinstance(results, dict):
            for key, value in results.items():
                print(f"  • {key}: {value}")
    
    print("\n" + "=" * 70)
    print("空间理论构造完成！")
    print("=" * 70)


if __name__ == "__main__":
    main()
